home *** CD-ROM | disk | FTP | other *** search
/ Collection of Internet / Collection of Internet.iso / msdos / lynx / source / www / library / implemen / htaaprot.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-10-25  |  17.0 KB  |  645 lines

  1.  
  2. /* MODULE                            HTAAProt.c
  3. **        PROTECTION FILE PARSING MODULE
  4. **
  5. ** AUTHORS:
  6. **    AL    Ari Luotonen    luotonen@dxcern.cern.ch
  7. **    MD    Mark Donszelmann    duns@vxdeop.cern.ch
  8. **
  9. ** HISTORY:
  10. **    20 Oct 93  AL    Now finds uid/gid for nobody/nogroup by name
  11. **            (doesn't use default 65534 right away).
  12. **            Also understands negative uids/gids.
  13. **    14 Nov 93  MD    Added VMS compatibility
  14. **    19 Nov 93  GB    Added MS-DOS support for Borland C++ v3.1
  15. **
  16. ** BUGS:
  17. **
  18. **
  19. */
  20.  
  21. #include"capalloc.h"
  22. #include"capstdio.h"
  23. #include <string.h>
  24. #ifndef VMS
  25. #ifndef MSDOS
  26. #include <pwd.h>    /* Unix password file routine: getpwnam()    */
  27. #include <grp.h>    /* Unix group file routine: getgrnam()        */
  28. #endif /* not MSDOS */
  29. #endif /* not VMS */
  30.  
  31. #include "HTUtils.h"
  32. #include "HTAAUtil.h"
  33. #include "HTAAFile.h"
  34. #include "HTLex.h"    /* Lexical analysor    */
  35. #include "HTAssoc.h"    /* Association list    */
  36. #include "HTAAProt.h"    /* Implemented here    */
  37.  
  38.  
  39. /*
  40. ** Protection setup caching
  41. */
  42. typedef struct {
  43.     char *    prot_filename;
  44.     HTAAProt *    prot;
  45. } HTAAProtCache;
  46.  
  47. PRIVATE HTList *  prot_cache    = NULL;    /* Protection setup cache.    */
  48. PRIVATE HTAAProt *default_prot    = NULL;    /* Default protection.        */
  49. PRIVATE HTAAProt *current_prot    = NULL;    /* Current protection mode    */
  50.                     /* which is set up by callbacks    */
  51.                     /* from the rule system when    */
  52.                     /* a "protect" rule is matched.    */
  53.  
  54.  
  55.  
  56. /* PRIVATE                            isNumber()
  57. **        DOES A CHARACTER STRING REPRESENT A NUMBER
  58. */
  59. PRIVATE BOOL isNumber ARGS1(CONST char *, s)
  60. {
  61.     CONST char *cur = s;
  62.  
  63.     if (!s || !*s) return NO;
  64.  
  65.     if (*cur == '-')
  66.     cur++;        /* Allow initial minus sign in a number */
  67.  
  68.     while (*cur) {
  69.     if (*cur < '0' || *cur > '9')
  70.         return NO;
  71.     cur++;
  72.     }
  73.     return YES;
  74. }
  75.  
  76. #ifdef VMS
  77.  
  78. /* PUBLIC                            HTAA_getUidName()
  79. **        GET THE USER ID NAME (VMS ONLY)
  80. ** ON ENTRY:
  81. **    No arguments.
  82. **
  83. ** ON EXIT:
  84. **    returns    the user name
  85. **        Default is "" (nobody).
  86. */
  87. PUBLIC char * HTAA_getUidName NOARGS
  88. {
  89.     if (current_prot && current_prot->uid_name
  90.           && (0 != strcmp(current_prot->uid_name,"nobody")) )
  91.        return(current_prot->uid_name);
  92.     else
  93.        return("");
  94. }
  95.  
  96. /* PUBLIC                            HTAA_getFileName
  97. **        GET THE FILENAME (VMS ONLY)
  98. ** ON ENTRY:
  99. **    No arguments.
  100. **
  101. ** ON EXIT:
  102. **    returns    the filename
  103. */
  104. PUBLIC char * HTAA_getFileName NOARGS
  105. {
  106.     if (current_prot && current_prot->filename)
  107.        return(current_prot->filename);
  108.     else
  109.        return("");
  110. }
  111.  
  112. #else /* not VMS */
  113.  
  114. /* PUBLIC                            HTAA_getUid()
  115. **        GET THE USER ID TO CHANGE THE PROCESS UID TO
  116. ** ON ENTRY:
  117. **    No arguments.
  118. **
  119. ** ON EXIT:
  120. **    returns    the uid number to give to setuid() system call.
  121. **        Default is 65534 (nobody).
  122. */
  123. PUBLIC int HTAA_getUid NOARGS
  124. {
  125. #ifndef MSDOS
  126.     struct passwd *pw = NULL;
  127.  
  128.     if (current_prot  &&  current_prot->uid_name) {
  129.     if (isNumber(current_prot->uid_name)) {
  130.         if (NULL != (pw = getpwuid(atoi(current_prot->uid_name)))) {
  131. #ifndef RELEASE
  132.         if (TRACE) fprintf(stderr,
  133.                    "%s(%s) returned (%s:%s:%d:%d:...)\n",
  134.                    "HTAA_getUid: getpwuid",
  135.                    current_prot->uid_name,
  136.                    pw->pw_name, pw->pw_passwd,
  137.                    pw->pw_uid, pw->pw_gid);
  138. #endif /* RELEASE */
  139.         return pw->pw_uid;
  140.         }
  141.     }
  142.     else {    /* User name (not a number) */
  143.         if (NULL != (pw = getpwnam(current_prot->uid_name))) {
  144. #ifndef RELEASE
  145.         if (TRACE) fprintf(stderr, "%s(\"%s\") %s (%s:%s:%d:%d:...)\n",
  146.                    "HTAA_getUid: getpwnam",
  147.                    current_prot->uid_name, "returned",
  148.                    pw->pw_name, pw->pw_passwd,
  149.                    pw->pw_uid, pw->pw_gid);
  150. #endif /* RELEASE */
  151.         return pw->pw_uid;
  152.         }
  153.     }
  154.     }
  155.     /*
  156.     ** Ok, then let's get uid for nobody.
  157.     */
  158.     if (NULL != (pw = getpwnam("nobody"))) {
  159. #ifndef RELEASE
  160.     if (TRACE) fprintf(stderr, "HTAA_getUid: Uid for `nobody' is %d\n",
  161.                pw->pw_uid);
  162. #endif /* RELEASE */
  163.     return pw->pw_uid;
  164.     }
  165. #endif /* not MSDOS */
  166.     /*
  167.     ** Ok, then use default.
  168.     */
  169.     return 65534;    /* nobody */
  170. }
  171.  
  172.  
  173.  
  174. /* PUBLIC                            HTAA_getGid()
  175. **        GET THE GROUP ID TO CHANGE THE PROCESS GID TO
  176. ** ON ENTRY:
  177. **    No arguments.
  178. **
  179. ** ON EXIT:
  180. **    returns    the uid number to give to setgid() system call.
  181. **        Default is 65534 (nogroup).
  182. */
  183. PUBLIC int HTAA_getGid NOARGS
  184. {
  185. #ifndef MSDOS
  186.     struct group *gr = NULL;
  187.  
  188.     if (current_prot  &&  current_prot->gid_name) {
  189.     if (isNumber(current_prot->gid_name)) {
  190.         if (NULL != (gr = getgrgid(atoi(current_prot->gid_name)))) {
  191. #ifndef RELEASE
  192.         if (TRACE) fprintf(stderr,
  193.                    "%s(%s) returned (%s:%s:%d:...)\n",
  194.                    "HTAA_getGid: getgrgid",
  195.                    current_prot->gid_name,
  196.                    gr->gr_name, gr->gr_passwd, gr->gr_gid);
  197. #endif /* RELEASE */
  198.         return gr->gr_gid;
  199.         }
  200.     }
  201.     else {    /* Group name (not number) */
  202.         if (NULL != (gr = getgrnam(current_prot->gid_name))) {
  203. #ifndef RELEASE
  204.         if (TRACE) fprintf(stderr,
  205.                    "%s(\"%s\") returned (%s:%s:%d:...)\n",
  206.                    "HTAA_getGid: getgrnam",
  207.                    current_prot->gid_name,
  208.                    gr->gr_name, gr->gr_passwd, gr->gr_gid);
  209. #endif /* RELEASE */
  210.         return gr->gr_gid;
  211.         }
  212.     }
  213.     }
  214.     /*
  215.     ** Ok, then let's get gid for nogroup.
  216.     */
  217.     if (NULL != (gr = getgrnam("nogroup"))) {
  218. #ifndef RELEASE
  219.     if (TRACE) fprintf(stderr, "HTAA_getGid: Gid for `nogroup' is %d\n",
  220.                gr->gr_gid);
  221. #endif /* RELEASE */
  222.     return gr->gr_gid;
  223.     }
  224. #endif /* not MSDOS */
  225.     /*
  226.     ** Ok, then use default.
  227.     */
  228.     return 65534;    /* nogroup */
  229. }
  230.  
  231. #endif /* not VMS */
  232.  
  233.  
  234. /* PRIVATE                            HTAA_setIds()
  235. **        SET UID AND GID (AS NAMES OR NUMBERS)
  236. **        TO HTAAProt STRUCTURE
  237. ** ON ENTRY:
  238. **    prot        destination.
  239. **    ids        is a string like "james.www" or "1422.69" etc.
  240. **            giving uid and gid.
  241. **
  242. ** ON EXIT:
  243. **    returns        nothing.
  244. */
  245. PRIVATE void HTAA_setIds ARGS2(HTAAProt *,    prot,
  246.                    CONST char *,    ids)
  247. {
  248.     if (ids) {
  249.     char *local_copy = NULL;
  250.     char *point;
  251.  
  252.     StrAllocCopy(local_copy, ids);
  253.     point = strchr(local_copy, '.');
  254.     if (point) {
  255.         *(point++) = (char)0;
  256.         StrAllocCopy(prot->gid_name, point);
  257.     }
  258.     else {
  259.         StrAllocCopy(prot->gid_name, "nogroup");
  260.     }
  261.     StrAllocCopy(prot->uid_name, local_copy);
  262.     FREE(local_copy);
  263.     }
  264.     else {
  265.     StrAllocCopy(prot->uid_name, "nobody");
  266.     StrAllocCopy(prot->gid_name, "nogroup");
  267.     }
  268. }
  269.  
  270.  
  271.  
  272. /* PRIVATE                        HTAA_parseProtFile()
  273. **        PARSE A PROTECTION SETUP FILE AND
  274. **        PUT THE RESULT IN A HTAAProt STRUCTURE
  275. ** ON ENTRY:
  276. **    prot        destination structure.
  277. **    fp        open protection file.
  278. **
  279. ** ON EXIT:
  280. **    returns        nothing.
  281. */
  282. PRIVATE void HTAA_parseProtFile ARGS2(HTAAProt *, prot,
  283.                       FILE *,      fp)
  284. {
  285.     if (prot && fp) {
  286.     LexItem lex_item;
  287.     char *fieldname = NULL;
  288.  
  289.     while (LEX_EOF != (lex_item = lex(fp))) {
  290.  
  291.         while (lex_item == LEX_REC_SEP)    /* Ignore empty lines */
  292.         lex_item = lex(fp);
  293.  
  294.         if (lex_item == LEX_EOF)        /* End of file */
  295.         break;
  296.  
  297.         if (lex_item == LEX_ALPH_STR) {    /* Valid setup record */
  298.         
  299.         StrAllocCopy(fieldname, lex_buffer);
  300.         
  301.         if (LEX_FIELD_SEP != (lex_item = lex(fp)))
  302.             unlex(lex_item);    /* If someone wants to use colon */
  303.                                 /* after field name it's ok, but */
  304.                                 /* not required. Here we read it.*/
  305.  
  306.         if (0==strncasecomp(fieldname, "Auth", 4)) {
  307.             lex_item = lex(fp);
  308.             while (lex_item == LEX_ALPH_STR) {
  309.             HTAAScheme scheme = HTAAScheme_enum(lex_buffer);
  310.             if (scheme != HTAA_UNKNOWN) {
  311.                 if (!prot->valid_schemes)
  312.                 prot->valid_schemes = HTList_new();
  313.                 HTList_addObject(prot->valid_schemes,(void*)scheme);
  314. #ifndef RELEASE
  315.                 if (TRACE) fprintf(stderr, "%s %s `%s'\n",
  316.                            "HTAA_parseProtFile: valid",
  317.                            "authentication scheme:",
  318.                            HTAAScheme_name(scheme));
  319. #endif /* RELEASE */
  320.             }
  321. #ifndef RELEASE
  322.             else if (TRACE) fprintf(stderr, "%s %s `%s'\n",
  323.                         "HTAA_parseProtFile: unknown",
  324.                         "authentication scheme:",
  325.                         lex_buffer);
  326. #endif /* RELEASE */
  327.             
  328.             if (LEX_ITEM_SEP != (lex_item = lex(fp)))
  329.                 break;
  330.             /*
  331.             ** Here lex_item == LEX_ITEM_SEP; after item separator
  332.             ** it is ok to have one or more newlines (LEX_REC_SEP)
  333.             ** and they are ignored (continuation line).
  334.             */
  335.             do {
  336.                 lex_item = lex(fp);
  337.             } while (lex_item == LEX_REC_SEP);
  338.             } /* while items in list */
  339.         } /* if "Authenticate" */
  340.  
  341.         else if (0==strncasecomp(fieldname, "mask", 4)) {
  342.             prot->mask_group = HTAA_parseGroupDef(fp);
  343.             lex_item=LEX_REC_SEP; /*groupdef parser read this already*/
  344. #ifndef RELEASE
  345.             if (TRACE) {
  346.             if (prot->mask_group) {
  347.                 fprintf(stderr,
  348.                     "HTAA_parseProtFile: Mask group:\n");
  349.                 HTAA_printGroupDef(prot->mask_group);
  350.             } else fprintf(stderr, "HTAA_parseProtFile: %s\n",
  351.                        "Mask group syntax error");
  352.             }
  353. #endif /* RELEASE */
  354.         } /* if "Mask" */
  355.  
  356.         else {    /* Just a name-value pair, put it to assoclist */
  357.  
  358.             if (LEX_ALPH_STR == (lex_item = lex(fp))) {
  359.             if (!prot->values)
  360.                 prot->values = HTAssocList_new();
  361.             HTAssocList_add(prot->values, fieldname, lex_buffer);
  362.             lex_item = lex(fp);  /* Read record separator */
  363. #ifndef RELEASE
  364.             if (TRACE) fprintf(stderr,
  365.                        "%s `%s' bound to value `%s'\n",
  366.                        "HTAA_parseProtFile: Name",
  367.                        fieldname, lex_buffer);
  368. #endif /* RELEASE */
  369.             }
  370.         } /* else name-value pair */
  371.  
  372.         } /* if valid field */
  373.  
  374.         if (lex_item != LEX_EOF  &&  lex_item != LEX_REC_SEP) {
  375. #ifndef RELEASE
  376.         if (TRACE) fprintf(stderr, "%s %s %d (that line ignored)\n",
  377.                    "HTAA_parseProtFile: Syntax error",
  378.                    "in protection setup file at line",
  379.                    lex_line);
  380. #endif /* RELEASE */
  381.         do {
  382.             lex_item = lex(fp);
  383.         } while (lex_item != LEX_EOF && lex_item != LEX_REC_SEP);
  384.         } /* if syntax error */
  385.     } /* while not end-of-file */
  386.     } /* if valid parameters */
  387. }
  388.  
  389.  
  390.  
  391.  
  392. /* PRIVATE                        HTAAProt_new()
  393. **        ALLOCATE A NEW HTAAProt STRUCTURE AND
  394. **        INITIALIZE IT FROM PROTECTION SETUP FILE
  395. ** ON ENTRY:
  396. **    cur_docname    current filename after rule translations.
  397. **    prot_filename    protection setup file name.
  398. **            If NULL, not an error.
  399. **    ids        Uid and gid names or numbers,
  400. **            examples:
  401. **                james    ( <=> james.nogroup)
  402. **                .www    ( <=> nobody.www)
  403. **                james.www
  404. **                james.69
  405. **                1422.69
  406. **                1422.www
  407. **
  408. **            May be NULL, defaults to nobody.nogroup.
  409. **            Should be NULL, if prot_file is NULL.
  410. **
  411. ** ON EXIT:
  412. **    returns        returns a new and initialized protection
  413. **            setup structure.
  414. **            If setup file is already read in (found
  415. **            in cache), only sets uid_name and gid
  416. **            fields, and returns that.
  417. */
  418. PRIVATE HTAAProt *HTAAProt_new ARGS3(CONST char *,    cur_docname,
  419.                      CONST char *,    prot_filename,
  420.                      CONST char *,    ids)
  421. {
  422.     HTList *cur = prot_cache;
  423.     HTAAProtCache *cache_item = NULL;
  424.     HTAAProt *prot;
  425.     FILE *fp;
  426.  
  427.     if (!prot_cache)
  428.     prot_cache = HTList_new();
  429.     
  430.     while (NULL != (cache_item = (HTAAProtCache*)HTList_nextObject(cur))) {
  431.     if (!strcmp(cache_item->prot_filename, prot_filename))
  432.         break;
  433.     }
  434.     if (cache_item) {
  435.     prot = cache_item->prot;
  436. #ifndef RELEASE
  437.     if (TRACE) fprintf(stderr, "%s `%s' already in cache\n",
  438.                "HTAAProt_new: Protection file", prot_filename);
  439. #endif /* RELEASE */
  440.     } else {
  441. #ifndef RELEASE
  442.     if (TRACE) fprintf(stderr,
  443.                "HTAAProt_new: Loading protection file `%s'\n",
  444.                prot_filename);
  445. #endif /* RELEASE */
  446.  
  447.     if (!(prot = (HTAAProt*)malloc(sizeof(HTAAProt))))
  448.         outofmem(__FILE__, "HTAAProt_new");
  449.  
  450.     prot->template    = NULL;
  451.     prot->filename    = NULL;
  452.     prot->uid_name    = NULL;
  453.     prot->gid_name    = NULL;
  454.     prot->valid_schemes = HTList_new();
  455.     prot->mask_group= NULL;        /* Masking disabled by defaults */
  456.     prot->values    = HTAssocList_new();
  457.  
  458.     if (prot_filename && NULL != (fp = fopen(prot_filename, "r"))) {
  459.         HTAA_parseProtFile(prot, fp);
  460.         fclose(fp);
  461.         if (!(cache_item = (HTAAProtCache*)malloc(sizeof(HTAAProtCache))))
  462.         outofmem(__FILE__, "HTAAProt_new");
  463.         cache_item->prot = prot;
  464.         cache_item->prot_filename = NULL;
  465.         StrAllocCopy(cache_item->prot_filename, prot_filename);
  466.         HTList_addObject(prot_cache, (void*)cache_item);
  467.     }
  468. #ifndef RELEASE
  469.     else if (TRACE) fprintf(stderr, "HTAAProt_new: %s `%s'\n",
  470.                 "Unable to open protection setup file",
  471.                 (prot_filename ? prot_filename : "(null)"));
  472. #endif /* RELEASE */
  473.     }
  474.  
  475.     if (cur_docname)
  476.     StrAllocCopy(prot->filename, cur_docname);
  477.     HTAA_setIds(prot, ids);
  478.  
  479.     return prot;
  480. }
  481.  
  482.  
  483.  
  484. /* PUBLIC                    HTAA_setDefaultProtection()
  485. **        SET THE DEFAULT PROTECTION MODE
  486. **        (called by rule system when a
  487. **        "defprot" rule is matched)
  488. ** ON ENTRY:
  489. **    cur_docname    is the current result of rule translations.
  490. **    prot_filename    is the protection setup file (second argument
  491. **            for "defprot" rule, optional)
  492. **    ids        contains user and group names separated by
  493. **            a dot, corresponding to the uid
  494. **            gid under which the server should run,
  495. **            default is "nobody.nogroup" (third argument
  496. **            for "defprot" rule, optional; can be given
  497. **            only if protection setup file is also given).
  498. **
  499. ** ON EXIT:
  500. **    returns        nothing.
  501. **            Sets the module-wide variable default_prot.
  502. */
  503. PUBLIC void HTAA_setDefaultProtection ARGS3(CONST char *,    cur_docname,
  504.                         CONST char *,    prot_filename,
  505.                         CONST char *,    ids)
  506. {
  507.     default_prot = NULL;    /* Not free()'d because this is in cache */
  508.  
  509.     if (prot_filename) {
  510.     default_prot = HTAAProt_new(cur_docname, prot_filename, ids);
  511.     } else {
  512. #ifndef RELEASE
  513.     if (TRACE) fprintf(stderr, "%s %s\n",
  514.                "HTAA_setDefaultProtection: ERROR: Protection file",
  515.                "not specified (obligatory for DefProt rule)!!\n");
  516. #endif /* RELEASE */
  517.     }
  518. }
  519.  
  520.  
  521.  
  522. /* PUBLIC                    HTAA_setCurrentProtection()
  523. **        SET THE CURRENT PROTECTION MODE
  524. **        (called by rule system when a
  525. **        "protect" rule is matched)
  526. ** ON ENTRY:
  527. **    cur_docname    is the current result of rule translations.
  528. **    prot_filename    is the protection setup file (second argument
  529. **            for "protect" rule, optional)
  530. **    ids        contains user and group names separated by
  531. **            a dot, corresponding to the uid
  532. **            gid under which the server should run,
  533. **            default is "nobody.nogroup" (third argument
  534. **            for "protect" rule, optional; can be given
  535. **            only if protection setup file is also given).
  536. **
  537. ** ON EXIT:
  538. **    returns        nothing.
  539. **            Sets the module-wide variable current_prot.
  540. */
  541. PUBLIC void HTAA_setCurrentProtection ARGS3(CONST char *,    cur_docname,
  542.                         CONST char *,    prot_filename,
  543.                         CONST char *,    ids)
  544. {
  545.     current_prot = NULL;    /* Not free()'d because this is in cache */
  546.  
  547.     if (prot_filename) {
  548.     current_prot = HTAAProt_new(cur_docname, prot_filename, ids);
  549.     } else {
  550.     if (default_prot) {
  551.         current_prot = default_prot;
  552.         HTAA_setIds(current_prot, ids);
  553. #ifndef RELEASE
  554.         if (TRACE) fprintf(stderr, "%s %s %s\n",
  555.                    "HTAA_setCurrentProtection: Protection file",
  556.                    "not specified for Protect rule",
  557.                    "-- using default protection");
  558. #endif /* RELEASE */
  559.     } else {
  560. #ifndef RELEASE
  561.         if (TRACE) fprintf(stderr, "%s %s %s\n",
  562.                    "HTAA_setCurrentProtection: ERROR: Protection",
  563.                    "file not specified for Protect rule, and",
  564.                    "default protection is not set!!");
  565. #endif /* RELEASE */
  566.     }
  567.     }
  568. }
  569.  
  570.  
  571.  
  572. /* PUBLIC                    HTAA_getCurrentProtection()
  573. **        GET CURRENT PROTECTION SETUP STRUCTURE
  574. **        (this is set up by callbacks made from
  575. **         the rule system when matching "protect"
  576. **         (and "defprot") rules)
  577. ** ON ENTRY:
  578. **    HTTranslate() must have been called before calling
  579. **    this function.
  580. **
  581. ** ON EXIT:
  582. **    returns    a HTAAProt structure representing the
  583. **        protection setup of the HTTranslate()'d file.
  584. **        This must not be free()'d.
  585. */
  586. PUBLIC HTAAProt *HTAA_getCurrentProtection NOARGS
  587. {
  588.     return current_prot;
  589. }
  590.  
  591.  
  592.  
  593. /* PUBLIC                    HTAA_getDefaultProtection()
  594. **        GET DEFAULT PROTECTION SETUP STRUCTURE
  595. **        AND SET IT TO CURRENT PROTECTION
  596. **        (this is set up by callbacks made from
  597. **         the rule system when matching "defprot"
  598. **         rules)
  599. ** ON ENTRY:
  600. **    HTTranslate() must have been called before calling
  601. **    this function.
  602. **
  603. ** ON EXIT:
  604. **    returns    a HTAAProt structure representing the
  605. **        default protection setup of the HTTranslate()'d
  606. **        file (if HTAA_getCurrentProtection() returned
  607. **        NULL, i.e. if there is no "protect" rule
  608. **        but ACL exists, and we need to know default
  609. **        protection settings).
  610. **        This must not be free()'d.
  611. ** IMPORTANT:
  612. **    As a side-effect this tells the protection system that
  613. **    the file is in fact protected and sets the current
  614. **    protection mode to default.
  615. */
  616. PUBLIC HTAAProt *HTAA_getDefaultProtection NOARGS
  617. {
  618.     if (!current_prot) {
  619.     current_prot = default_prot;
  620.     default_prot = NULL;
  621.     }    
  622.     return current_prot;
  623. }
  624.  
  625.  
  626.  
  627. /* SERVER INTERNAL                    HTAA_clearProtections()
  628. **        CLEAR DOCUMENT PROTECTION MODE
  629. **        (ALSO DEFAULT PROTECTION)
  630. **        (called by the rule system)
  631. ** ON ENTRY:
  632. **    No arguments.
  633. **
  634. ** ON EXIT:
  635. **    returns    nothing.
  636. **        Frees the memory used by protection information.
  637. */
  638. PUBLIC void HTAA_clearProtections NOARGS
  639. {
  640.     current_prot = NULL;    /* These are not freed because    */
  641.     default_prot = NULL;    /* they are actually in cache.    */
  642. }
  643.  
  644.  
  645.